<!DOCTYPE html>
<html>
<head>
    <title>Simple Harmonic Motion Graph</title>
</head>
<body>
    <canvas id="shmCanvas" width="550" height="400"></canvas>
    <script>
        const canvas = document.getElementById('shmCanvas');
        const ctx = canvas.getContext('2d');

        // --- Style and Configuration ---
        const cx = 80;         // Canvas origin x
        const cy = 200;        // Canvas origin y
        const timeScale = 25;  // Pixels per second
        const dispScale = 15;  // Pixels per cm

        // Function to transform graph coordinates to canvas coordinates
        function toCanvas(t, x) {
            return {
                x: cx + t * timeScale,
                y: cy - x * dispScale
            };
        }

        // --- Drawing Functions ---

        // 1. Draw Axes
        function drawAxes() {
            ctx.beginPath();
            ctx.strokeStyle = 'black';
            ctx.fillStyle = 'black';
            ctx.lineWidth = 2;

            // t-axis (horizontal)
            const tAxisStart = toCanvas(-2, 0);
            const tAxisEnd = toCanvas(17, 0);
            ctx.moveTo(tAxisStart.x, tAxisStart.y);
            ctx.lineTo(tAxisEnd.x, tAxisEnd.y);

            // Arrowhead for t-axis
            ctx.moveTo(tAxisEnd.x, tAxisEnd.y);
            ctx.lineTo(tAxisEnd.x - 10, tAxisEnd.y - 5);
            ctx.moveTo(tAxisEnd.x, tAxisEnd.y);
            ctx.lineTo(tAxisEnd.x - 10, tAxisEnd.y + 5);

            // x-axis (vertical)
            const xAxisStart = toCanvas(0, -12);
            const xAxisEnd = toCanvas(0, 12);
            ctx.moveTo(xAxisStart.x, xAxisStart.y);
            ctx.lineTo(xAxisEnd.x, xAxisEnd.y);

            // Arrowhead for x-axis
            ctx.moveTo(xAxisStart.x, xAxisStart.y);
            ctx.lineTo(xAxisStart.x - 5, xAxisStart.y + 10);
            ctx.moveTo(xAxisStart.x, xAxisStart.y);
            ctx.lineTo(xAxisStart.x + 5, xAxisStart.y + 10);

            ctx.stroke();
        }

        // 2. Draw Curve
        function drawCurve() {
            ctx.beginPath();
            ctx.lineWidth = 2;
            const tStart = -0.5;
            const tEnd = 16;
            const dt = 0.05;

            // The function is x(t) = 10 * cos( (pi/6)t + pi/3 )
            const amplitude = 10;
            const omega = Math.PI / 6;
            const phi0 = Math.PI / 3;

            let firstPoint = true;
            for (let t = tStart; t <= tEnd; t += dt) {
                const x = amplitude * Math.cos(omega * t + phi0);
                const p = toCanvas(t, x);
                if (firstPoint) {
                    ctx.moveTo(p.x, p.y);
                    firstPoint = false;
                } else {
                    ctx.lineTo(p.x, p.y);
                }
            }
            ctx.stroke();
        }

        // 3. Draw Labels and Points
        function drawLabelsAndPoints() {
            ctx.fillStyle = 'black';
            ctx.strokeStyle = 'black';
            
            // Axis labels
            ctx.font = 'italic 20px Times New Roman';
            ctx.textAlign = 'center';
            ctx.textBaseline = 'bottom';
            ctx.fillText('x/cm', toCanvas(0, 12).x - 30, toCanvas(0, 12).y);
            ctx.textAlign = 'left';
            ctx.textBaseline = 'top';
            ctx.fillText('t/s', toCanvas(17, 0).x, toCanvas(17, 0).y + 5);

            // Origin label
            ctx.textAlign = 'right';
            ctx.textBaseline = 'top';
            ctx.fillText('O', toCanvas(0, 0).x - 5, toCanvas(0, 0).y + 5);

            // Vertical axis ticks and labels
            ctx.font = '20px Times New Roman';
            ctx.textAlign = 'right';
            ctx.textBaseline = 'middle';
            
            // Label for 5
            const p5 = toCanvas(0, 5);
            ctx.moveTo(p5.x, p5.y);
            ctx.lineTo(p5.x - 5, p5.y);
            ctx.fillText('5', p5.x - 10, p5.y);

            // Label for -10
            const p_neg10 = toCanvas(0, -10);
            ctx.moveTo(p_neg10.x, p_neg10.y);
            ctx.lineTo(p_neg10.x - 5, p_neg10.y);
            ctx.fillText('-10', p_neg10.x - 10, p_neg10.y);
            
            ctx.stroke();

            // Dashed line for -10
            ctx.beginPath();
            ctx.setLineDash([4, 3]);
            const troughT = 4; // t where x = -10
            const troughPos = toCanvas(troughT, -10);
            ctx.moveTo(p_neg10.x, p_neg10.y);
            ctx.lineTo(troughPos.x, troughPos.y);
            ctx.stroke();
            ctx.setLineDash([]); // Reset to solid line

            // Horizontal axis labels and points
            ctx.textAlign = 'center';
            ctx.textBaseline = 'top';
            const labelY = cy + 10;
            
            // Label and point for 7
            const p7 = toCanvas(7, 0);
            ctx.fillText('7', p7.x, labelY);
            ctx.beginPath();
            ctx.arc(p7.x, p7.y, 4, 0, 2 * Math.PI);
            ctx.fill();

            // Label and point for 10
            const p10 = toCanvas(10, 0);
            ctx.fillText('10', p10.x, labelY);
            ctx.beginPath();
            ctx.arc(p10.x, p10.y, 4, 0, 2 * Math.PI);
            ctx.fill();

            // Label and point for 13
            const p13 = toCanvas(13, 0);
            ctx.fillText('13', p13.x, labelY);
            ctx.beginPath();
            ctx.arc(p13.x, p13.y, 4, 0, 2 * Math.PI);
            ctx.fill();
        }

        // --- Main Execution ---
        drawAxes();
        drawCurve();
        drawLabelsAndPoints();
    </script>
</body>
</html>